///////////////////////////////////////////////////////////////////////
//  CS 3716 (Winter 2012), Assignment #4                       		 //
//  Program File Name: RecList.java                           		 //
//       Student Name: Jonathan Hart-Wall, Adam Murphy         		 //
//					   Yifu Liang, Joshua Dowling			   		 //
//         Login Name: jcwhw1, agm264 , n96yl, n23jdd                //
//              MUN #: 200933455, 200933133, 200565679, 200703684    //
///////////////////////////////////////////////////////////////////////

import java.util.ArrayList;
import java.util.Collections;
import java.io.*;

public class RecList {

	private String name;
	private ArrayList<MovieRec> movieList;
	private ArrayList<String> history;
	private String verifier;
	
	/**
	 * RecList Constructor
	 * @param name
	 * @param movieList
	 * @param history
	 * @param verifier
	 */
	public RecList(String name, ArrayList<MovieRec> movieList, ArrayList<String> history, String verifier){
		this.name = name;
		this.movieList = movieList;
		this.history = history;
		this.verifier = null;
	}
	
	/**
	 * Accessor Method to return ArrayList<MovieRec> movieList
	 */
	public ArrayList<MovieRec> getMovieList()
	{
		return movieList;
	}
	
	/**
	 * Accessor method to return name
	 */
	public String getName() {
		return name;
	}
	
	/**
	 * Mutator method to set name to String name
	 */
	public void setName(String name) {
		this.name = name;
	}

	/**
	 * Accessor method to return verifier
	 */
	public String getVerifier() {
		return verifier;
	}
	
	/**
	 * Mutator method to set verifier to String verifier
	 */
	public void verify(String verifier) {
		this.verifier = verifier;
	}
	
	/**
	 * Method to view History, by printing all elements of ArrayList<String> history
	 */
	public void viewHistory(){
		for (int i = 0; i < history.size(); i++){
			System.out.println(history.get(i));
		}
	}
	
	/**
	 * Method to add History to ArrayList<String> history using String action and String user 
	 * Method creates a new string hist by combining action and user, and adds it to history
	 */
	public void addHistory(String action, String user){
		String hist = action +" " +user;
		history.add(hist);
	}
	
	/**
	 * Method to display all MovieRec Objects in RecList
	 * Method prints the toString of MovieRec Object in RecList.
	 */
	public String display()
	{
		String display = "";
		for (int i = 0; i < movieList.size(); i++){
			display = display + movieList.get(i).toString() + "\n";
		}
		return display.trim();
	}
	
	/**
	 * Method to display all MovieRec Objects in RecList, but they are sorted alphabetically.
	 * Method first creates new ArrayList<MovieRec> dS, then copies the contents of movieList in it.
	 * Then dS is sorted by Collections.sort using a custom Comparator MRCompare, which sorts them by name,
	 * and if the names are the same, sorts them in increasing order of year. The method then prints the contents
	 * of dS, and dS is emptied when the display is done.
	 */
	public String displaySorted(){
		ArrayList<MovieRec> dS = new ArrayList<MovieRec>();

		for(int i = 0; i < movieList.size(); i++){
			dS.add(movieList.get(i));
		}
		
		Collections.sort(dS, new MRCompare());
		
		String display = "";
		for (int i = 0; i < dS.size(); i++){
			display = display + dS.get(i).toString() + "\n";
		}
		
		dS.clear();
		return display.trim();
	}
	
	/**
	 * Method to search ArrayList<MovieRec> movieList for MovieRec Object with String name and int year. 
	 * If found, it will return the MovieRec Object, or it will return null.
	 */
	public MovieRec search(String name, int year) throws MovieNotFoundException, EmptyListException
	{
		if(movieList.size() == 0){
			throw new EmptyListException();
		}
		else{
			for(int i=0; i < movieList.size(); i++){
				if(name.equalsIgnoreCase(movieList.get(i).getName()) && year == movieList.get(i).getReleaseYear()){
					return movieList.get(i);
				}
			}
		}
		throw new MovieNotFoundException();
	}
	
	/**
	 * Method to search ArrayList<MovieRec> movieList for MovieRec Object(s) with String genre.
	 * If found, it will return an ArrayList of MovieRec Object(s) with String genre.
	 */
	public ArrayList<MovieRec> search(String genre) throws MovieNotFoundException, EmptyListException
	{
		ArrayList<MovieRec> searchResults = new ArrayList<MovieRec>();
		if(movieList.isEmpty()){
			throw new EmptyListException();
		}
		String[] searchGenres = genre.split(" / ");

		for(int i = 0; i < movieList.size(); i++){
			String[] genres = movieList.get(i).getGenre().split(" / ");
			boolean added = false;
			for(int j = 0; j < genres.length; j++){
				for (int k = 0; k < searchGenres.length; k++)
				{
					if(genres[j].equalsIgnoreCase(searchGenres[k]))
					{
						searchResults.add(movieList.get(i));
						added = true;
						break;
					}
				}
				if (added)
					break;
			}
		}
		if (searchResults.size() == 0)
			throw new MovieNotFoundException();
		return searchResults;
	}
	
	/**
	 * Method to update all contents of RecList to an external text file.
	 */
	public void update(String fileLocation) throws FileNotFoundException, IOException
	{
		PrintWriter pw = new PrintWriter(new File(fileLocation + "//" + name + ".dat"));
		pw.println(name);
		pw.println(verifier);
		pw.println();
		
		for (MovieRec movieRec : movieList)
			pw.println(movieRec.getName() + "#" + movieRec.getReleaseYear() + "#" + movieRec.getGenre() + "#" + movieRec.getRating() + "#" + movieRec.getSubmitter());

		pw.println();
		
		for (String historyLine : history)
			pw.println(historyLine);
		pw.close();
	}	
}